import random
from asyncio.base_events import Server
from datetime import datetime
from uuid import uuid1

from django.db.models import Q
from rest_framework.generics import ListAPIView
from rest_framework.pagination import PageNumberPagination
from rest_framework.response import Response
from rest_framework.views import APIView
from urllib3 import request

from cart import models
from cart.cartser import CartSer
from cart.models import CartModel
from order.models import UserCouponModel, OrderModel, goumai, OrderDatailModel
from order.ser import UserCouponSer, OrderSer, UserOrderSer, GouwuSer
from user.models import UserModels
from user.userser import UserSer
from utils.AliPayModel import AliPaySDK
from utils.authentication import MyAuthentication
from django.db import transaction

from utils.myRedis import MyRedis, rediss


# 订单商品
# Create your views here.
class OrderListView(APIView):
    authentication_classes = [MyAuthentication]

    def get(self, request):
        user = request.query_params.get("user", None)
        nam = models.CartModel.objects.filter(user=user, selected=True)
        if not nam:
            return Response({"msg": "用户不存在"})
        new = CartSer(nam, many=True)
        return Response({"msg": "ok", "data": new.data})


# 积分机制
class OrderDataView(APIView):
    authentication_classes = [MyAuthentication]

    def get(self, request):
        user = request.query_params.get("user")
        nam = models.UserModels.objects.filter(id=user).first()
        new = UserSer(nam)
        return Response({"msg": "ok", "data": new.data})


# 优惠卷机制
class UserCouponView(APIView):
    authentication_classes = [MyAuthentication]

    def get(self, request):
        user = request.query_params.get("user", None)
        if user is None:
            return Response({"msg": "用户不存在优惠卷"})
        cc = UserCouponModel.objects.filter(user=user, is_del=1)
        new = UserCouponSer(cc, many=True)
        return Response({"msg": "ok", "data": new.data})


def getno():
    return datetime.now().strftime("%Y%m%d%H%M%S") + str(random.randint(1000, 9999))


# 订单生成
class CreateOrderView(APIView):
    authentication_classes = [MyAuthentication]

    def post(self, request):
        user = request.data.get("user", None)  # 用户ID
        paytype = request.data.get("paytype", None)  # 支付方式
        score = request.data.get("score", None)  # 积分
        coupon = request.data.get("coupon", None)  # 优惠卷
        if user is None:
            return Response("用户不存在")
        if paytype is None:
            return Response("请选择支付方式")
        # 事务
        save_id = transaction.savepoint()

        red = rediss.getstr(user)
        if red:
            return Response("订单生成中请稍后")

        rediss.setstr(user, str(uuid1()))
        try:
            orderData = {
                "user": user,  # 用户
                "paytype": paytype,  # 支付方式
                "orderno": getno(),  # 订单号
                "totalprice": 0,  # 总价
                "realprice": 0  # 实付金额
            }
            # 获取购物车中的勾选的商品数据
            # 根据购物车商品获取总价
            cartdata = CartModel.objects.filter(user=user, selected=True)
            if cartdata.__len__() == 0:
                return Response({"msg": "购物车为空"})
            for i in cartdata:
                # 根据商品表的外键直接获取价格然后进行累加
                orderData["totalprice"] += i.course.price

            # 实际付款价格设置默认值
            orderData['realprice'] = orderData['totalprice']
            # 验证积分扣钱机制
            # 获取用户的整条数据
            userdata = UserModels.objects.filter(id=user).first()
            # 如果前端穿过来的积分或者兑换的积分大于用户自己的积分就成立
            if score is not None and score <= userdata.score:
                orderData["realprice"] = float(orderData["totalprice"]) - (score / 10)
                orderData["score"] = score
            # 验证优惠卷
            if coupon is not None:
                # 查询用户所拥有的优惠卷
                coupondata = UserCouponModel.objects.filter(id=coupon, user=user).first()
                # 用户的价格与所拥有的优惠卷的条件对比
                if orderData["totalprice"] > coupondata.coupon.condition:
                    # 成立后完成实际付款的修改
                    orderData["realprice"] -= coupondata.coupon.price
                    orderData["coupon"] = coupon
            ser = OrderSer(data=orderData)
            if ser.is_valid():
                ser.save()
                # 添加订单商品详细信息
                for cart in cartdata:
                    dataildata = {
                        'order': ser.data["id"],
                        'courseid': cart.course.id,
                        'coursename': cart.course.name,
                        'courseprice': cart.course.price,
                        'cover': cart.course.cover,
                        'type': cart.course.level
                    }
                    sir = UserOrderSer(data=dataildata)
                    if sir.is_valid():
                        sir.save()
                # 删除购物车里的数据
                cartdata.delete()

            transaction.savepoint_commit(save_id)
            rediss.delstr(user)
            return Response({"msg": "订单生成成功", "data": ser.data})
        except:
            transaction.savepoint_rollback(save_id)
            return Response({"msg": "订单生成失败"})


# 支付宝支付功能
class AilPayView(APIView):
    def get(self, request):
        orderid = request.query_params.get("order_id", None)
        Server = OrderModel.objects.filter(id=orderid).first()
        if Server is None:
            return Response("无订单信息")
        ali = AliPaySDK()
        linkstr = ali.page_pay(Server.orderno, Server.realprice, "向浮光课堂付款")
        return Response(linkstr)



# 支付完成页面
class OrderPayCheck(APIView):
    authentication_classes = [MyAuthentication]

    def get(self, request):
        data = request.query_params
        ali = AliPaySDK()
        success = ali.check_sign(data.dict())
        if success:
            order = OrderModel.objects.filter(orderno=data.get("out_trade_no")).first()
            if order:
                order.status = 2
                order.payno = data.get("seller_id")
                order.paytime = data.get("timestamp")
                order.save()
                if order.score > 0:
                    user = UserModels.objects.get(id=order.user.id)
                    user.score = user.secor - order.score
                    user.save()

                if order.coupon is not None:
                    cou = models.CourseModel.objects.filter(id=order.coupon).first()
                    cou.is_del = 1
                    cou.save()

                ser = OrderSer(order)
                sercc=OrderDatailModel.objects.filter(order=order.id).first()
                cdata={
                    "userid":order.user.id,
                    'Courseid':sercc.courseid
                }
                ff=GouwuSer(data=cdata)
                if ff.is_valid():
                    ff.save()

                return Response({"msg": "ok", "data": {"paytime": ser.data["paytime"], "total": ser.data["realprice"],
                                                       "course": ser.data["orderdatailmodel_set"]}})
            else:
                return Response({"msg": "支付失败"})


class Page(PageNumberPagination):
    page_size = 5
    max_page_size = 10
    page_size_query_param = "size"
    page_query_param = "page"

# 个人空间的商品列表展示
class userOrder(ListAPIView):
    queryset = OrderModel.objects.all()
    serializer_class = OrderSer
    pagination_class = Page
    def get_queryset(self):
        query = Q()
        userid = self.request.query_params.get("userid")
        print(userid)
        if userid:
            query &= Q(user=userid)
        return self.queryset.filter(query)
